package com.taxshare.seller.service;

import cn.hutool.core.map.MapUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.core.util.XmlUtil;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.taxshare.freemark.utils.FreemarkUtil;
import com.taxshare.response.beans.Response;
import com.taxshare.seller.constant.CodeConstant;
import com.taxshare.seller.constant.ResultConstant;
import com.taxshare.seller.entity.EquipmentEntity;
import com.taxshare.seller.entity.GoldenTaxPlateInfoEntity;
import com.taxshare.seller.entity.SellerInvoiceEntity;
import com.taxshare.seller.mapper.InvoicedMapper;
import com.taxshare.seller.remote.ApiClientService;
import com.taxshare.seller.service.sst.IntJsonUtil;
import com.taxshare.seller.util.InvoiceHelper;
import com.taxshare.seller.util.TransformationUtil;
import com.taxshare.seller.view.dto.GoldenTaxPlateDTO;
import com.taxshare.seller.view.dto.InterfaceDTO;
import com.taxshare.seller.view.dto.SellerInvoiceDTO;
import com.taxshare.seller.view.vo.SellerInvoiceVO;
import com.taxshare.tools.util.DateUtil;
import com.taxshare.tools.util.UUIDUitl;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections.MapUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Isolation;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;

import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * 远程
 */
@Service
@Transactional(propagation = Propagation.REQUIRED, isolation = Isolation.READ_COMMITTED)
@Slf4j
public class RemoteService extends ServiceImpl<InvoicedMapper, SellerInvoiceEntity> {

    @Autowired
    ApiClientService apiClientService;

    @Autowired
    GoldenTaxPlateService goldenTaxPlateService;

    @Autowired
    EquipmentService  equipmentService;

    @Value("${zzsfp.url}")
    private String zzsfpUrl;

    /**
     * 远程抄报
     *
     * @param sellerInvoiceVO
     * @return
     */
    public Response report(SellerInvoiceVO sellerInvoiceVO) throws Exception {
        Response res = new Response();
        //获取开票设备 A9对应明源开票 其他则税神通开票
        String sellerTaxNo = sellerInvoiceVO.getSellerTaxNo();
        EquipmentEntity equipmentEntity = equipmentService.getOne(new QueryWrapper<EquipmentEntity>().eq("seller_tax_no", sellerTaxNo).eq("disable","1"));
        if (null == equipmentEntity) {
            res.setCode("T0001");
            res.setMsg("同步失败，该纳税人识别号对应的设备未添加或开启，请检查！");
            return res;
        }
        //设备类型
        String equipmentMode = equipmentEntity.getEquipmentMode();
        if (CodeConstant.A9.equals(equipmentMode)) {
            res = reportA9(sellerInvoiceVO);
        } else {
            res = reportSST(sellerInvoiceVO,equipmentEntity);
        }
        return res;
    }

    /**
     * A9远程抄报
     *
     * @param sellerInvoiceVO
     * @return
     */
    public Response reportA9(SellerInvoiceVO sellerInvoiceVO) throws Exception {
        String url = zzsfpUrl + "busiInterface";
        String interfaceCode = "EI.NEWYCCB.U.EC.INTRA";
        String fplx = InvoiceHelper.transFplxdm(sellerInvoiceVO.getInvoiceType());
        sellerInvoiceVO.setInvoiceType(fplx);
        String ykInvoiceData = FreemarkUtil.getTemplateObj("/report.ftl", sellerInvoiceVO);
        String xmlData = InvoiceHelper.getXmlData(ykInvoiceData, interfaceCode, sellerInvoiceVO.getInvoiceType(), null);
        InterfaceDTO interfaceDTO = new InterfaceDTO();
        interfaceDTO.setXmlData(xmlData);
        interfaceDTO.setUrl(url);
/*        Response response = apiClientService.callSales(interfaceDTO);
        HashMap hashMap = new HashMap();
        if (("T0000").equals(response.getCode())) {
            String reqcontent = response.getMsg();
            ResponseCommonYccbVO responsecommonyccb = (ResponseCommonYccbVO) XmlInterfaceUtils.XmltoBean(reqcontent, ResponseCommonYccbVO.class);
            String code = responsecommonyccb.getCommonYccbs().getCommonYccb().getCode();
            String mess = responsecommonyccb.getCommonYccbs().getCommonYccb().getMess();
            hashMap.put("code", code);
            hashMap.put("mess", mess);
            return Response.success(hashMap);
        } else {
            return Response.error();
        }*/
        return Response.success();
    }

    /***
     * 税神通远程抄报
     * @param reqVo
     * @return
     */
    public Response reportSST(SellerInvoiceVO reqVo,EquipmentEntity equipmentEntity) {
        String json = IntJsonUtil.sendRepTax(equipmentEntity, reqVo.getSellerTaxNo(), reqVo.getInvoiceType());
        SellerInvoiceDTO sellerInvoiceDTO = new SellerInvoiceDTO();
        sellerInvoiceDTO.setBw(json);
        Response response = apiClientService.callSST(sellerInvoiceDTO);
        String result = (String) response.getData();
        com.alibaba.fastjson.JSONObject jsonObject = (JSONObject) JSON.parse(result);
        String code = jsonObject.getString("code");
        String msg = jsonObject.getString("msg");
        if (!"00000".equals(code)) {
            Response res = new Response();
            res.setCode("T0001");
            res.setMsg(msg);
            return res;
        }
        return Response.success();
    }

    /**
     * 远程清卡
     * @param sellerInvoiceVO
     * @return
     * @throws Exception
     */
    public Response clearCard(SellerInvoiceVO sellerInvoiceVO) throws Exception {
        Response res = new Response();
        //获取开票设备 A9对应明源开票 其他则税神通开票
        String sellerTaxNo = sellerInvoiceVO.getSellerTaxNo();
        EquipmentEntity equipmentEntity = equipmentService.getOne(new QueryWrapper<EquipmentEntity>().eq("seller_tax_no", sellerTaxNo).eq("disable","1"));
        if (null == equipmentEntity) {
            res.setCode("T0001");
            res.setMsg("同步失败，该纳税人识别号对应的设备未添加或开启，请检查！");
            return res;
        }
        //设备类型
        String equipmentMode = equipmentEntity.getEquipmentMode();
        if (CodeConstant.A9.equals(equipmentMode)) {
            res = clearCardA9(sellerInvoiceVO);
        } else {
            res = clearCardSST(sellerInvoiceVO,equipmentEntity);
        }
        return res;
    }

    /**
     * A9服务器清卡
     * @param sellerInvoiceVO
     * @return
     * @throws Exception
     */
    public Response clearCardA9(SellerInvoiceVO sellerInvoiceVO) throws Exception {
        String ykInvoiceData = FreemarkUtil.getTemplateObj("/clearCard.ftl", sellerInvoiceVO);
        String url = zzsfpUrl + "busiInterface";
        String interfaceCode = "EI.NEWYCQK.U.EC.INTRA";
        String fplx = InvoiceHelper.transFplxdm(sellerInvoiceVO.getInvoiceType());
        String xmlData = InvoiceHelper.getXmlData(ykInvoiceData, interfaceCode, sellerInvoiceVO.getSellerTaxNo(), null);
        InterfaceDTO interfaceDTO = new InterfaceDTO();
        interfaceDTO.setXmlData(xmlData);
        interfaceDTO.setUrl(url);
/*
        Response response = apiClientService.callSales(interfaceDTO);
        HashMap hashMap = new HashMap();
        if (("T0000").equals(response.getCode())) {
            String reqcontent = response.getMsg();
            ResponseCommonYccbVO responsecommonyccb = (ResponseCommonYccbVO) XmlInterfaceUtils.XmltoBean(reqcontent, ResponseCommonYccbVO.class);
            String code = responsecommonyccb.getCommonYccbs().getCommonYccb().getCode();
            String mess = responsecommonyccb.getCommonYccbs().getCommonYccb().getMess();
            hashMap.put("code", code);
            hashMap.put("mess", mess);
            return Response.success(hashMap);
        } else {
            return Response.error();
        }
*/
        return Response.success();
    }

    /**
     * 税神通清卡
     * @param sellerInvoiceVO
     * @param equipmentEntity
     * @return
     * @throws Exception
     */
    public Response clearCardSST(SellerInvoiceVO sellerInvoiceVO,EquipmentEntity equipmentEntity) throws Exception {
        String json = IntJsonUtil.cleanRepTax(equipmentEntity, sellerInvoiceVO.getSellerTaxNo(), sellerInvoiceVO.getInvoiceType());
        SellerInvoiceDTO sellerInvoiceDTO = new SellerInvoiceDTO();
        sellerInvoiceDTO.setBw(json);
        Response response = apiClientService.callSST(sellerInvoiceDTO);
        String result = (String) response.getData();
        com.alibaba.fastjson.JSONObject jsonObject = (JSONObject) JSON.parse(result);
        String code = jsonObject.getString("code");
        String msg = jsonObject.getString("msg");
        if (!"00000".equals(code)) {
            Response res = new Response();
            res.setCode("T0001");
            res.setMsg(msg);
            return res;
        }
        return Response.success();
    }


    /**
     * 同步抄报信息
     *
     * @param
     * @return
     */
    public Response syncReportInfo(GoldenTaxPlateDTO goldenTaxPlateDTO) {
        Response response = new Response();
        String sellerTaxNo = goldenTaxPlateDTO.getSellerTaxNo();
        String sellerName = goldenTaxPlateDTO.getSellerName();
        //根据税盘不同处理
        EquipmentEntity equipmentEntity = equipmentService.getOne(new QueryWrapper<EquipmentEntity>().eq("seller_tax_no", sellerTaxNo));
        if (equipmentEntity == null || CodeConstant.COMM_CODE_0.equals(equipmentEntity.getDisable())) {
            return Response.error("SEL_038");
        }
        if (CodeConstant.A9.equals(equipmentEntity.getEquipmentMode())) {
            response = syncReportInfoA9(sellerTaxNo);
        } else {
            response = syncReportInfoSST(equipmentEntity, sellerName);
        }
        return response;
    }

    /**
     * 同步抄报信息SST(1)
     * @param equipmentEntity
     * @return
     */
    public Response syncReportInfoSST(EquipmentEntity equipmentEntity,String sellerName) {
        Response res = new Response<>();
        if (StrUtil.isNotBlank(equipmentEntity.getInvoiceTypeList())) {
            List<String> list = Arrays.asList(equipmentEntity.getInvoiceTypeList().split(","));
            if (!list.isEmpty() && list != null) {
                for (String invoiceType : list) {
                    //发票类型转换（金税盘调用）
//                    String invoiceType = TransformationUtil.transInvoiceTypeSST(s);
                    res = callSyncInterface(equipmentEntity, invoiceType,sellerName);
                }
            }
        }
        return res;
    }

    /**
     * 同步抄报信息SST(2)
     * @param equipmentEntity
     * @param invoiceType
     */
    private Response callSyncInterface(EquipmentEntity equipmentEntity, String invoiceType, String SellerName) {
        Response res = new Response<>();
        String json = IntJsonUtil.synchronizateRepTax(equipmentEntity, invoiceType);
        SellerInvoiceDTO sellerRemoteVo = new SellerInvoiceDTO();
        sellerRemoteVo.setBw(json);
        try {
            Response response = apiClientService.callSST(sellerRemoteVo);
            String result = (String) response.getData();
            JSONObject jsonObject = (JSONObject) JSON.parse(result);
            String code = jsonObject.getString("code");
            String msg = jsonObject.getString("msg");
            if (CodeConstant.THIRD_PARTY_SUCCESS.equals(code)) {
                try {
                    syncGoldenTaxPlateSST(jsonObject, SellerName);
                } catch (Exception e) {
                    log.info("同步抄报信息失败！{}", e);
                    return Response.error(CodeConstant.ERROR, "同步失败，请稍后重试！");
                }
            } else {
                res.setMsg(msg);
                res.setCode(code);
                return res;
            }

        } catch (Exception e) {
            return Response.error(CodeConstant.ERROR, "同步抄报接口异常");
        }
        res.setCode(CodeConstant.T0000);
        return res;
    }

    /**
     * 同步抄报信息SST(3)
     * @param
     */
    public void syncGoldenTaxPlateSST(JSONObject jsonObject, String sellerName) {
        Map<String, String> map = (Map<String, String>) jsonObject.get("data");
        GoldenTaxPlateInfoEntity goldenTaxPlateInfoEntity = new GoldenTaxPlateInfoEntity();
        goldenTaxPlateInfoEntity.setSellerTaxNo(jsonObject.getString("nsrsbh"));
        goldenTaxPlateInfoEntity.setSellerName(sellerName);
        goldenTaxPlateInfoEntity.setInvoiceTypeNo(TransformationUtil.transSstInvoiceType(map.get("fplxdm")));
        goldenTaxPlateInfoEntity.setLockDate(DateUtil.getFormatDate(map.get("ssrq")));
        goldenTaxPlateInfoEntity.setCopyTaxDate(DateUtil.getFormatDate(map.get("bsqsrq")));
        goldenTaxPlateInfoEntity.setLastTaxDate(DateUtil.getFormatDate(map.get("zxbsrq")));
        goldenTaxPlateInfoEntity.setOfflineMoney(map.get("ljlxkpje"));
        goldenTaxPlateInfoEntity.setSingleQuota(map.get("dzkpxe"));
        goldenTaxPlateInfoEntity.setOfflineTime(map.get("lxkpsc"));
        QueryWrapper<GoldenTaxPlateInfoEntity> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("seller_tax_no", jsonObject.getString("nsrsbh"))
                .eq("invoice_type_no", TransformationUtil.transSstInvoiceType(map.get("fplxdm")));
        GoldenTaxPlateInfoEntity entity = goldenTaxPlateService.getOne(queryWrapper);
        if (entity == null) {
            goldenTaxPlateInfoEntity.setUuid(UUIDUitl.UUID32(false));
            goldenTaxPlateService.save(goldenTaxPlateInfoEntity);
        } else {
            goldenTaxPlateService.update(goldenTaxPlateInfoEntity, queryWrapper);
        }
    }


    /**
     * 同步抄报信息(A9)
     * @param nsr
     * @return
     */
    public Response syncReportInfoA9(String nsr) {
        if (StrUtil.hasBlank(nsr)) {
            return Response.error(ResultConstant.RET_P0001_CODE, ResultConstant.RET_P0001_MSG);
        }
        Response<Object> res = new Response<>();
        Map<String, String> fmap = new HashMap<>();
        fmap.put("fplx", "");
        String syncReport = FreemarkUtil.getTemplateObj("syncReport.ftl", fmap);
        String url = zzsfpUrl + "jspxxcxInterface";
        String interfaceCode = "EI.JSPXXCX.U.EC.INTRA";
        String xmlData = InvoiceHelper.getXmlData(syncReport, interfaceCode, nsr, null);
        InterfaceDTO interfaceDTO = new InterfaceDTO();
        interfaceDTO.setUrl(url);
        interfaceDTO.setXmlData(xmlData);
        Response response = apiClientService.callSales(interfaceDTO);
        if (CodeConstant.T0000.equals(response.getCode())) {
            String data = (String) response.getData();
            Map<String, Object> map = XmlUtil.xmlToMap(data);
            try {
                goldenTaxPlateService.syncGoldenTaxPlate(map);
            } catch (Exception e) {
                log.info("同步抄报信息错误:{e}", e);
            }
        }else{
            res.setMsg(response.getMsg());
            res.setCode(response.getCode());
            return res;
        }
        return Response.success();
    }
}